﻿using System;
using System.Collections.Generic;
using System.Net;
using System.Threading;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Ink;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;
using Microsoft.Silverlight.Testing;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using Salient.Net;
using Salient.Net.Tests;

namespace GatewayTests.Silverlight4
{
    [TestClass]
    public class Tests : SilverlightTest
    {
        public class Wrapper
        {
            public string ResponseText;
        }

        [TestMethod]
        [Asynchronous]
        public void Throttle()
        {
            IGateway gw = new GatewayFactory().DefaultGateway;

            const int requestCount = 60;

            for (int i = 0; i < requestCount; i++)
            {
                int i1 = i;
                ThreadPool.QueueUserWorkItem(o => gw.BeginGetResponse("http://stackauth.com/1.0/sites?s=1" + i1,
                    ar =>
                    {
                        var st = (GatewayRequestState)ar.AsyncState;
                        // give a +/- 2% buffer on the interval
                        Assert.IsTrue(st.RequestInterval > (gw.ThrottleInterval * .98), "Throttle violated " + st.RequestInterval);
                        if (i1 == requestCount - 1)
                        {
                            EnqueueTestComplete();
                        }
                    },
                    rs => new Wrapper
                    {
                        ResponseText = rs.Response.GetResponseText()
                    }));
            }
        }

        [TestMethod]
        [Asynchronous]
        public void Cached()
        {


            IGateway gateway = new GatewayFactory().DefaultGateway;
            gateway.Cache.DefaultCacheDuration = new TimeSpan(0, 0, 5);

            bool flag = false;
            ThreadPool.QueueUserWorkItem((o) =>
            {
                var result = gateway.BeginGetResponse("http://api.stackoverflow.com/1.0/questions/3354893?key=qgAq_KfDu0KYzlNG-qaTuw", null,
                                                      rs => new Wrapper
                                                      {
                                                          ResponseText = rs.Response.GetResponseText()
                                                      });

                result.AsyncWaitHandle.WaitOne();
                if (result.Exception != null)
                {
                    throw new Exception(null, result.Exception);
                }
                Assert.IsFalse(((GatewayRequestState)result.AsyncState).Cached, "first request should not be cached");

                result = gateway.BeginGetResponse("http://api.stackoverflow.com/1.0/questions/3354893?key=qgAq_KfDu0KYzlNG-qaTuw", null,
                                                  rs => new Wrapper
                                                  {
                                                      ResponseText = rs.Response.GetResponseText()
                                                  });

                result.AsyncWaitHandle.WaitOne();
                if (result.Exception != null)
                {
                    throw new Exception(null, result.Exception);
                }
                Assert.IsTrue(((GatewayRequestState)result.AsyncState).Cached, "second request should be cached");
                EnqueueTestComplete();
            });


        }


        [TestMethod]
        [Asynchronous]
        public void CacheExpired()
        {


            IGateway gateway = new GatewayFactory().DefaultGateway;
            gateway.Cache.DefaultCacheDuration = new TimeSpan(0, 0, 5);

            bool flag = false;
            ThreadPool.QueueUserWorkItem((o) =>
            {
                var result = gateway.BeginGetResponse("http://api.stackoverflow.com/1.0/questions/3354893?key=qgAq_KfDu0KYzlNG-qaTuw", null,
                                                      rs => new Wrapper
                                                      {
                                                          ResponseText = rs.Response.GetResponseText()
                                                      });

                result.AsyncWaitHandle.WaitOne();
                if (result.Exception != null)
                {
                    throw new Exception(null, result.Exception);
                }
                Assert.IsFalse(((GatewayRequestState)result.AsyncState).Cached, "first request should not be cached");

                new AutoResetEvent(false).WaitOne(10000);


                result = gateway.BeginGetResponse("http://api.stackoverflow.com/1.0/questions/3354893?key=qgAq_KfDu0KYzlNG-qaTuw", null,
                                                          rs => new Wrapper
                                                          {
                                                              ResponseText = rs.Response.GetResponseText()
                                                          });

                result.AsyncWaitHandle.WaitOne();

                if (result.Exception != null)
                {
                    throw new Exception(null, result.Exception);
                }
                Assert.IsFalse(((GatewayRequestState)result.AsyncState).Cached, "second request should not be cached");
                EnqueueTestComplete();
            });


        }
    }
}